package org.wavefar.lib.ui.widget;

import android.content.Context;
import android.util.AttributeSet;
import android.view.View;
import android.view.ViewGroup;

import java.util.ArrayList;
import java.util.List;

/**
 * 流式布局
 * @author summer
 */
public class FlowLayout extends ViewGroup
{

	public FlowLayout(Context context, AttributeSet attrs, int defStyle)
	{
		super(context, attrs, defStyle);

	}

	public FlowLayout(Context context, AttributeSet attrs)
	{
		this(context, attrs, 0);
	}

	public FlowLayout(Context context)
	{
		this(context, null);
	}

	@Override
	protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec)
	{
		int sizeWidth = MeasureSpec.getSize(widthMeasureSpec);
		int modeWidth = MeasureSpec.getMode(widthMeasureSpec);
		int sizeHeight = MeasureSpec.getSize(heightMeasureSpec);
		int modeHeight = MeasureSpec.getMode(heightMeasureSpec);

		// wrap_content
		int width = 0;
		int height = 0;


		int lineWidth = 0;
		int lineHeight = 0;


		int cCount = getChildCount();

		for (int i = 0; i < cCount; i++)
		{
			View child = getChildAt(i);

			measureChild(child, widthMeasureSpec, heightMeasureSpec);

			MarginLayoutParams lp = (MarginLayoutParams) child
					.getLayoutParams();


			int childWidth = child.getMeasuredWidth() + lp.leftMargin
					+ lp.rightMargin;

			int childHeight = child.getMeasuredHeight() + lp.topMargin
					+ lp.bottomMargin;


			if (lineWidth + childWidth > sizeWidth - getPaddingLeft() - getPaddingRight())
			{

				width = Math.max(width, lineWidth);

				lineWidth = childWidth;

				height += lineHeight;
				lineHeight = childHeight;
			} else

			{

				lineWidth += childWidth;

				lineHeight = Math.max(lineHeight, childHeight);
			}

			if (i == cCount - 1)
			{
				width = Math.max(lineWidth, width);
				height += lineHeight;
			}
		}



		setMeasuredDimension(
				modeWidth == MeasureSpec.EXACTLY ? sizeWidth : width + getPaddingLeft() + getPaddingRight(),
				modeHeight == MeasureSpec.EXACTLY ? sizeHeight : height + getPaddingTop()+ getPaddingBottom()
		);

	}


	private List<List<View>> mAllViews = new ArrayList<>();

	private List<Integer> mLineHeight = new ArrayList<>();

	@Override
	protected void onLayout(boolean changed, int l, int t, int r, int b)
	{
		mAllViews.clear();
		mLineHeight.clear();

		int width = getWidth();

		int lineWidth = 0;
		int lineHeight = 0;

		List<View> lineViews = new ArrayList<>();

		int cCount = getChildCount();

		for (int i = 0; i < cCount; i++)
		{
			View child = getChildAt(i);
			MarginLayoutParams lp = (MarginLayoutParams) child
					.getLayoutParams();

			int childWidth = child.getMeasuredWidth();
			int childHeight = child.getMeasuredHeight();


			if (childWidth + lineWidth + lp.leftMargin + lp.rightMargin > width - getPaddingLeft() - getPaddingRight())
			{

				mLineHeight.add(lineHeight);

				mAllViews.add(lineViews);


				lineWidth = 0;
				lineHeight = childHeight + lp.topMargin + lp.bottomMargin;

				lineViews = new ArrayList<>();
			}
			lineWidth += childWidth + lp.leftMargin + lp.rightMargin;
			lineHeight = Math.max(lineHeight, childHeight + lp.topMargin
					+ lp.bottomMargin);
			lineViews.add(child);

		}// for end

		mLineHeight.add(lineHeight);
		mAllViews.add(lineViews);



		int left = getPaddingLeft();
		int top = getPaddingTop();


		int lineNum = mAllViews.size();

		for (int i = 0; i < lineNum; i++)
		{

			lineViews = mAllViews.get(i);
			lineHeight = mLineHeight.get(i);

			int lineViewSize = lineViews.size();
			for (int j = 0; j < lineViewSize; j++)
			{
				View child = lineViews.get(j);

				if (child.getVisibility() == View.GONE)
				{
					continue;
				}

				MarginLayoutParams lp = (MarginLayoutParams) child
						.getLayoutParams();

				int lc = left + lp.leftMargin;
				int tc = top + lp.topMargin;
				int rc = lc + child.getMeasuredWidth();
				int bc = tc + child.getMeasuredHeight();

				child.layout(lc, tc, rc, bc);

				left += child.getMeasuredWidth() + lp.leftMargin
						+ lp.rightMargin;
			}
			left = getPaddingLeft() ; 
			top += lineHeight ; 
		}

	}


	@Override
	public LayoutParams generateLayoutParams(AttributeSet attrs)
	{
		return new MarginLayoutParams(getContext(), attrs);
	}

}